package com.freecloud.whispered.oss.service.impl;


import cn.hutool.core.date.DatePattern;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.RandomUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.core.util.URLUtil;
import cn.hutool.crypto.SecureUtil;
import cn.hutool.json.JSONUtil;
import com.freecloud.framework.config.FreeCloudConfig;
import com.freecloud.framework.constant.Constant;
import com.freecloud.framework.request.Query;
import com.freecloud.framework.service.AbstractBaseService;
import com.freecloud.framework.utils.ImageUtil;
import com.freecloud.whispered.oss.OSSFactory;
import com.freecloud.whispered.oss.entity.SysOssEntity;
import com.freecloud.whispered.oss.repository.SysOssDao;
import com.freecloud.whispered.oss.service.SysOssService;
import org.apache.commons.io.FileUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;

import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.net.URISyntaxException;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;


@Service("sysOssService")
public class SysOssServiceImpl extends AbstractBaseService<SysOssEntity,Long,SysOssDao> implements SysOssService {

	private Logger logger = LoggerFactory.getLogger(getClass());

	@Autowired
	private FreeCloudConfig freeCloudConfig;

	@Autowired
	private SysOssDao sysOssDao;
//	@Autowired
//	private NetConnectorService netConnectorService;
//	@Autowired
//	private BaseUsersService baseUsersService;
//	@Autowired
//	private BaseUsersImportService baseUsersImportService;
//	@Autowired
//	private UserOtherHistoryService userOtherHistoryService;
//	@Autowired
//	private SysConfigService sysConfigService;



//	@Override
//	public void deleteBatch(Long[] ids){
//
//		if(ids == null || ids.length < 1)
//		{
//			return;
//		}
//		SysOssEntity ossObj = null;
//		for(int i = 0;i < ids.length ; i++)
//		{
//			ossObj = sysOssDao.queryObject (ids[i]);
//
//			try
//			{
//				OSSFactory.build().delete (ossObj.getUrl ());
//			}
//			catch (Exception e)
//			{
//
//			}
//
//			sysOssDao.delete (ids[i]);
//		}
//	}

	@Override
	public List<SysOssEntity> queryUserFileList(Map<String, Object> map)
	{
//		return sysOssDao.queryUserFileList (map);
		return null;
	}

	@Override
	public SysOssEntity uploadFile(String path) throws URISyntaxException, IOException {
		return uploadFile(path,false);
	}

	@Override
	public SysOssEntity uploadFile(String path,boolean isSaveLocalOss) throws IOException {
        if(StrUtil.isEmpty (path))
        {
            return null;
        }
		Map<String,Object> dataMap = new HashMap<> ();
		dataMap.put ("url",path);

		List<SysOssEntity> ossList = sysOssDao.findAll(Query.getExample(dataMap,SysOssEntity.class));
		if(ossList != null && ossList.size () > 0)
		{
			return ossList.get (0);
		}

        File fileObj = getImageFile (path);

        Object result = saveUploadFile(fileObj,null,isSaveLocalOss);
        if(result == null || result instanceof String){
            return null;
        }

        Map<String,Object> map = (Map<String,Object>)result;

        if(map.get("id") == null){
            return null;
        }
        return sysOssDao.getOne(Long.valueOf(map.get("id").toString()));
	}

	@Override
	public File saveLocationFile(MultipartFile multFile)
	{
		if(multFile == null)
		{
			return null;
		}

		String toFilePath = getUploadRelativePath(multFile.getOriginalFilename ());

		return saveLocationFile( multFile,toFilePath);
	}

	@Override
	public File saveLocationFile(MultipartFile multFile, String path) {
		if(multFile == null)
		{
			return null;
		}

		String basePath = StrUtil.isNotEmpty (freeCloudConfig.getUploadPath()) ? freeCloudConfig.getUploadPath() : StrUtil.isNotBlank(Constant.ROOTPATH) ? Constant.ROOTPATH : FileUtil.getCanonicalPath(new File(""));

		String toFilePath = basePath + path;

		File locationFile = null;
		locationFile = FileUtil.file (locationFile,toFilePath);

		try
		{
			FileUtils.copyInputStreamToFile(multFile.getInputStream(), locationFile);
		}
		catch (Exception e)
		{
		    logger.error("saveLocationFile error : ",e);
		}

		return locationFile;
	}

	@Override
	public File getImageFile(String urlPath){
		File file = null;
		try
		{
			String toFilePath = Constant.ROOTPATH + "/upload/images/" + DateUtil.date ().getTime () + ".jpg";

			urlPath = URLUtil.decode(urlPath);

			ImageUtil.downloadFile (urlPath, toFilePath);

			file = FileUtil.file (toFilePath);

		}
		catch (Exception e)
		{
			logger.error("获取网络图片，并下载到本地错误：",e);
		}
		return file;
	}

	@Transactional
	@Override
	public Object saveUploadFile(Object file, Map<String, Object> params,boolean isLocal) throws IOException {
		//临时保存到本地
		File fileObj = null;
		//上传文件
		String url;

		Map<String,Object> returnDataMap = new HashMap<> ();

		try{

		    if(file instanceof MultipartFile ){

                MultipartFile multipartFile = (MultipartFile)file;
                if(isLocal){
                    url = getUploadRelativePath(multipartFile.getOriginalFilename ());
                    fileObj =  saveLocationFile(multipartFile,url);
                } else {
                    fileObj =  saveLocationFile(multipartFile);
                    url = OSSFactory.build().upload( com.freecloud.framework.utils.FileUtil.readBytes (fileObj));
                }
            }else{
                fileObj = (File)file;
                url = fileObj.getPath();
            }

			String md5Key = SecureUtil.md5 (fileObj);

			Map<String,Object> dataMap = new HashMap<>();
			dataMap.put ("md5",md5Key);

			List<SysOssEntity> ossList = queryList (dataMap);


			SysOssEntity ossEntity = null;
			if(ossList == null || ossList.size () < 1)
			{
				//保存文件信息
				ossEntity = new SysOssEntity();
				ossEntity.setUrl(url);
				ossEntity.setSize (com.freecloud.framework.utils.FileUtil.size (fileObj));
                if(file instanceof MultipartFile ){
                    MultipartFile multipartFile = (MultipartFile)file;
                    ossEntity.setFileName (multipartFile.getOriginalFilename ());
                    ossEntity.setFileType (multipartFile.getContentType ());
                }
				ossEntity.setCreateDate(new Date());
				ossEntity.setMd5 (md5Key);

				if(ossEntity.getFileType ().indexOf ("image") >= 0)
				{
					BufferedImage imageObj = ImageIO.read(fileObj);

					ossEntity.setWidth (imageObj.getWidth ());
					ossEntity.setHeight (imageObj.getHeight ());

					Map<String,String> fileInfoMap = com.freecloud.framework.utils.FileUtil.getFileExifMap(fileObj);
					if(fileInfoMap != null)
					{
						String fileInfo = JSONUtil.toJsonStr (fileInfoMap);

						ossEntity.setFileInfo (fileInfo);
					}
				}

				sysOssDao.save(ossEntity);
			}
			else
			{
				if(!isLocal){
					OSSFactory.build().delete (url);
				}

				ossEntity = ossList.get (0);
			}
			//删除本地文件
			com.freecloud.framework.utils.FileUtil.del (fileObj);

			//TODO 保存用户与文件关系
			//saveUserOss(ossEntity, params);

			String actionType = params.get("action") != null ? params.get("action").toString() : null;

			if(StrUtil.isNotEmpty (actionType))
			{
				//为ckeditor上传，单独返回固定格式
				if("ckeditor".equals (actionType))
				{
					String callback = params.get("CKEditorFuncNum").toString();
					StringBuilder ckeditorHtml = new StringBuilder("<script type=\"text/javascript\">");

					ckeditorHtml.append ("window.parent.CKEDITOR.tools.callFunction(" + callback + ",'" + ossEntity.getUrl () + "','')");
					ckeditorHtml.append ("</script>");

					return ckeditorHtml.toString ();
				}
			}

			returnDataMap.put ("id",ossEntity.getId ());
			returnDataMap.put ("url",ossEntity.getUrl ());
			returnDataMap.put("fullUrl",ossEntity.getFullUrl ());
			returnDataMap.put ("size",ossEntity.getSize ());
			returnDataMap.put ("width",ossEntity.getWidth ());
			returnDataMap.put ("height",ossEntity.getHeight ());
			returnDataMap.put ("fileType",ossEntity.getFileType ());


		}catch (Exception e){
			logger.error("saveFile Error : ",e);
		}finally {
			//删除本地文件
			if(fileObj != null){
				FileUtil.del (fileObj);
			}

		}
		return returnDataMap;
	}

	/**
	 * 获取保存文件相对路径
	 * @param fileName
	 * @return
	 */
	private String getUploadRelativePath(String fileName)
	{
		DateUtil.format (DateUtil.date (), DatePattern.PURE_DATE_FORMAT);
		String toFilePath = "/upload/" + DateUtil.format (DateUtil.date (), DatePattern.PURE_DATE_FORMAT) + "/";

		String fileSuffix = fileName.substring(fileName.lastIndexOf(".") + 1);

		String randStr = RandomUtil.randomString (6);

		toFilePath += DateUtil.date ().getTime() + randStr + "." + fileSuffix;

		return toFilePath;
	}

	/**
	 * 证件文字识别《中国身份证号、驾驶证》
	 * 根据证件号识别结果，完善到基础用户中
	 * @param obj
	 */
//	public void certificateOCR(UserOssEntity obj)
//	{
//		if(obj == null || obj.getFileid () == null)
//		{
//			return;
//		}
//
//		SysOssEntity ossObj = sysOssDao.queryObject (obj.getFileid ());
//		if(ossObj == null || StrUtil.isEmpty (ossObj.getFullUrl ()))
//		{
//			return;
//		}
//
//		Map<String,Object> map = new HashMap<> ();
//		map.put ("Base64_image",ossObj.getFullUrl ());
//
//		long netid = sysConfigService.getValueLong ("commonOCR_Net_Id",0L);
//
//		String txtOcrResult = netConnectorService.requestConnector (netid,map);
//		if(StrUtil.isEmpty (txtOcrResult))
//		{
//			return;
//		}
//
//		//图片识别，证件分类
//		String type = null;
//		if(txtOcrResult.indexOf ("驾驶证") >= 0)
//		{
//			type = "1";
//		}
//		else if(txtOcrResult.indexOf ("公民身份号码") >= 0)
//		{
//			type = "2";
//		}
//
//		if(StrUtil.isEmpty (type))
//		{
//			return;
//		}
//
//		String resultStr = null;
//		//证件识别
//		if("1".equals (type))
//		{
//			resultStr = drivingOCR( ossObj);
//		}
//		else if("2".equals (type))
//		{
//			resultStr = idcardOCR(  ossObj);
//		}
//
//		//处理数据
//
//		if(StrUtil.isEmpty (resultStr))
//		{
//			return;
//		}
//		JSONObject idcarObj = JSONUtil.parseObj (resultStr);
//		if(StrUtil.isEmpty (idcarObj.getStr ("words_result_num")) )
//		{
//			return;
//		}
//		else if(idcarObj.getInt ("words_result_num") < 1)
//		{
//			return;
//		}
//
//		JSONObject idcarResult = idcarObj.getJSONObject ("words_result");
//
//		String name = idcarResult.getByPath ("姓名.words") != null ? idcarResult.getByPath ("姓名.words").toString () : null;
//		String sex = idcarResult.getByPath ("性别.words") != null ? idcarResult.getByPath ("性别.words").toString () : null;
//		String birsday = idcarResult.getByPath ("出生.words") != null ? idcarResult.getByPath ("出生.words").toString () : null;
//		String mz = idcarResult.getByPath ("民族.words") != null ? idcarResult.getByPath ("民族.words").toString () : null;
//		String address = idcarResult.getByPath ("住址.words") != null ? idcarResult.getByPath ("住址.words").toString () : null;
//		String idcar = idcarResult.getByPath ("公民身份号码.words") != null ? idcarResult.getByPath ("公民身份号码.words").toString () : null;
//		if(StrUtil.isEmpty (idcar))
//		{
//			idcar = idcarResult.getByPath ("证号.words") != null ? idcarResult.getByPath ("证号.words").toString () : null;
//		}
//
//		if(StrUtil.isEmpty (idcar))
//		{
//			return;
//		}
//
//		Map<String,Object> queryMap = new HashMap<> ();
//		queryMap.put ("idno",idcar);
//
//		List<BaseUsersEntity> baseUserList = baseUsersService.queryList (queryMap);
//		if(baseUserList != null && !baseUserList.isEmpty ())
//		{
//			if(baseUserList.size () > 1)
//			{
//				//有多个数据，记录到用户导入表，之后处理
//
//				BaseUsersImportEntity userImport = new BaseUsersImportEntity();
//
//				userImport.setName (name);
//				userImport.setSex (sex);
//				userImport.setNation (mz);
//				userImport.setAddress (address);
//				userImport.setIdno (idcar);
//				userImport.setBirthday (DateUtil.parse (birsday));
//				userImport.setCreatetime (DateUtil.date ());
//
//				baseUsersImportService.save (userImport);
//
//				return;
//			}
//			//验证是否与当前用户为同一用户，非同一用户单独处理
//			if(!baseUserList.get (0).getUserid ().equals (obj.getUserid ()))
//			{
//				BaseUsersImportEntity userImport = new BaseUsersImportEntity();
//
//				userImport.setName (name);
//				userImport.setSex (sex);
//				userImport.setNation (mz);
//				userImport.setAddress (address);
//				userImport.setIdno (idcar);
//				userImport.setBirthday (DateUtil.parse (birsday));
//				userImport.setRemark ("图片识别用户异常--" + obj.getUserid () + "--" + idcar);
//				userImport.setCreatetime (DateUtil.date ());
//
//				baseUsersImportService.save (userImport);
//				return;
//			}
//		}
//
//		BaseUsersEntity currentUser = baseUsersService.queryObject (obj.getUserid ());
//		if(currentUser == null)
//		{
//			currentUser = new BaseUsersEntity();
//		}
//		currentUser.setName (name);
//		currentUser.setSex (sex);
//		currentUser.setNation (mz);
//		currentUser.setAddress (address);
//		currentUser.setIdno (idcar);
//		currentUser.setBirthday (DateUtil.parse (birsday));
//
//		baseUsersService.update (currentUser);
//
//		if(!"1".equals (type))
//		{
//			return;
//		}
//
//		String firstDate = idcarResult.getByPath ("初次领证日期.words") != null ? idcarResult.getByPath ("初次领证日期.words").toString () : null;
//		String drivClass = idcarResult.getByPath ("准驾车型.words") != null ? idcarResult.getByPath ("准驾车型.words").toString () : null;
//		String validYear = idcarResult.getByPath ("有效期限.words") != null ? idcarResult.getByPath ("有效期限.words").toString () : null;
//		String validFirstDate = idcarResult.getByPath ("有效起始日期.words") != null ? idcarResult.getByPath ("有效起始日期.words").toString () : null;
//		String nationality = idcarResult.getByPath ("国籍.words") != null ? idcarResult.getByPath ("国籍.words").toString () : null;
//
//		UserOtherHistoryEntity otherHistory = new UserOtherHistoryEntity();
//
//		otherHistory.setUserid (obj.getUserid ());
//		otherHistory.setPurpose ("驾驶证");
//		if(StrUtil.isNotEmpty (firstDate))
//		{
//			otherHistory.setUsetime (DateUtil.parse (firstDate));
//		}
//		otherHistory.setAddress (nationality);
//		otherHistory.setRemark (drivClass + "--" + validFirstDate + "--" + validYear);
//
//		otherHistory.setCreatetime (DateUtil.date ());
//
//		userOtherHistoryService.save (otherHistory);
//	}
//
//	/**
//	 * 身份证号处理
//	 * @param ossObj
//	 */
//	private String idcardOCR(SysOssEntity ossObj)
//	{
//		Map<String,Object> map = new HashMap<> ();
//		map.put ("Base64_image",ossObj.getFullUrl ());
//		map.put ("id_card_side","front");
//
//		long netid = sysConfigService.getValueLong ("idcardOCR_Net_Id",0L);
//
//		return netConnectorService.requestConnector (netid,map);
//	}
//
//	/**
//	 * 驾驶证识别
//	 * @param ossObj
//	 */
//	private String drivingOCR(SysOssEntity ossObj)
//	{
//		Map<String,Object> map = new HashMap<> ();
//		map.put ("Base64_image",ossObj.getFullUrl ());
//
//		long netid = sysConfigService.getValueLong ("drivingOCR_Net_Id",0L);
//
//		return netConnectorService.requestConnector (netid,map);
//	}

}
